/* busLib.h - vxBus subsystem header file */

/* Copyright (c) 2005 Wind River Systems, Inc. */

/* 
modification history
--------------------
01c,20sep05,pdg  Fixed warning(SPR #112565)
01b,01sep05,mdo  Add vxb prefix
01a,10aug05,mdo  Phase in new access method
17Jan05,tor  written
*/

#ifndef _INC_BUSLIB_H
#define _INC_BUSLIB_H
#define _INC_BUSCONNECTLIB_H

#ifdef __cplusplus
extern "C" {
#endif

/* includes */

#include <sllLib.h>

/* defines */

/* vxbDevRegInfo->devID */
#define VXB_DEVID_DEVICE    0
#define VXB_DEVID_BUSCTRL   1

/* vxbDevRegInfo->busID */
#define VXB_BUSID_LOCAL             1   /* processor local bus */
#define VXB_BUSID_PLB               1   /* alt name for local bus */
#define VXB_BUSID_NEXUS             1   /* alt name for local bus */
#define VXB_BUSID_VME               2   /* VME */
#define VXB_BUSID_PCI               3   /* PCI */
#define VXB_BUSID_PCIX              4   /* PCI w/ PCI-X ext */
#define VXB_BUSID_PCIEXPRESS        5   /* PCI w/ PCI-Express ext */
#define VXB_BUSID_HYPERTRANSPORT    6   /* PCI w/ HyperTransport ext */
#define VXB_BUSID_RAPIDIO           7   /* RapidIO */

/* vxbDevRegInfo->busVer */
#define BUS_VERSION_1           1

#define MAX_DRV_NAME_LEN        31  /* 31-byte device names */

/* vxbDevIterate flags */
#define VXB_ITERATE_INSTANCES   1   /* instances */
#define VXB_ITERATE_ORPHANS     2   /* dev w/o drv */
#define VXB_ITERATE_VERBOSE     8   /* print diagnostics while running */

/* method used for unlinking a device from the driver */

#define VXB_METHOD_DRIVER_UNLINK        1

/* 0x1b-0xff: standard MethodIDs reserved for future use */

#define FIRST_CUSTOM_BUS_ACCESS_METHOD  0x00000100


/* byte-order and other bus access method flags */


/* flags for operation and debug 0x01000000 ... 0x80000000 */
#define BUSAF_VERBOSE           0x01000000

/*
 * FreeBSD methods use the address of a set of descriptions
 * as the method ID.  This macro, when expanded, fits into
 * the vxbDeviceMethod structure defined below.
 */
#define DEVMETHOD(NAME, FUNC) { (UINT32)&NAME##_desc, (FUNCPTR) FUNC }
#define METHOD_DECL(NAME)   IMPORT char NAME##_desc[];

typedef struct vxbDeviceMethod device_method_t;

/* forward structure/typedefs definitions */

typedef struct vxbDev BUS_DEVICE;
typedef struct vxbDev * BUS_DEVICE_ID;

typedef struct vxbAccessList HARDWARE_ACCESS;

typedef struct drvBusFuncs DRIVER_INITIALIZATION;
typedef struct vxbDevRegInfo DRIVER_REGISTRATION;
typedef struct vxbDeviceMethod DRIVER_METHOD;

/* typedefs */

/*
 *  An alternative method for bus controllers to provide the
 *  methods used by downstream devices.  This structure is
 *  provided so that the controller can provide a null-terminated
 *  list of method/handler pairs.
 *
 *  When a driver fetches the access methods, the standard methods
 *  are used first.  If the method is not one of the standard
 *  methods (specified in the vxbAccessList structure), or if the
 *  method specified is NULL in the controller's standard methods,
 *  then the vxbAccessMethodsGet() routine searches through any 
 *  methods listed in the pMethods field of the vxbAccessList
 *  structure.
 *
 *  In addition, this structure is used by all devices to provide
 *  services to OS modules such as power management.
 */

struct vxbDeviceMethod
    {
    UINT32      devMethodId;
    FUNCPTR     handler;
    };

/*===============================================================
*
* vxbBusTypeInfo - structure containing busType entry points
*
*  This structure provides entry points into the busType
*  for use by the bus sub-system during initialization and
*  operation.
*
*/

struct vxbBusTypeInfo
    {
    UINT32  busID;      /* busID */
    struct vxbBusTypeInfo * pNext;

/*===============================================================
*
*  The first routines are used during system boot, during
*  bus enumeration and configuration.
*/

    /* init1 */

    STATUS (*busTypeInit1)
        (
        );

    /* init2 */

    STATUS (*busTypeInit2)
        (
        );

    /* connect */

    STATUS (*busTypeConnect)
        (
        );

    /* check for new devices */

    BOOL (*busTypeNewDevPresent)
        (
        );

    /* check whether device and driver match */

    BOOL (*busDevMatch)
        (
        struct vxbDevRegInfo * pDriver,
        struct vxbDev * pDev
        );

    };


/*
 * Keep track of busses which are known to be present on the system.
 * This is only used internally, so the structure definition is here
 * instead of in the header file.
 */

struct vxbBusPresent
    {
    struct vxbBusPresent *     pNext;
    struct vxbBusTypeInfo *    pBusType;
    struct vxbDev *     pCtlr;
    struct vxbDev *     instList;
    struct vxbDev *     devList;
    };

/*
 *  This structure identifies the driver to the bus subsystem.
 *  It is used for driver registration with the bus subsystem.
 *
 *  Each driver or bus controller calls the vxbDevRegister()
 *  routine (prototype is shown below) with a pointer to a
 *  structure declared by the driver.  The information in the
 *  structure is static, so it can be included in the driver's
 *  initialized data segment.
 *
 *  This structure should never be used directly.  Instead,
 *  each bus type defines a structure of its own, with this
 *  structure as the first element (included, not as a pointer).
 *  The bus-defined structure may contain additional information,
 *  such as DEV_ID and VEND_ID on the PCI bus.  To get access
 *  to these structures, include the bus{TYPE}Lib.h file, e.g.
 *  "pciBusLib.h" or "busRioLib.h".
 */

struct vxbDevRegInfo
    {

    /* for next bus type */

    struct vxbDevRegInfo * pNext;

    /* device or bus controller: BUS_DEVID_DEVICE or BUS_DEVID_BUSCTRL */
    UINT32  devID;

    /* bus type and bus subsystem version */
    UINT32  busID;
    UINT32  busVer;

    /* dev/drv name */
    char    drvName[MAX_DRV_NAME_LEN+1];

    /* default registration functions */
    struct drvBusFuncs * pDrvBusFuncs;
    struct vxbDeviceMethod * pMethods;

    /* NULL probe routine indicates always true */

    BOOL (*devProbe)
        (
    struct vxbDev * pDevInfo    /* device info */
    );

    };

/*===============================================================
*
* drvBusFuncs - structure containing driver entry points
*
*  This structure provides entry points into the driver
*  for use by the bus sub-system during initialization and
*  operation.
*
*/

struct drvBusFuncs
    {

/*===============================================================
*
*  The first routines are used during system boot, during
*  bus enumeration and configuration.
*/

    /* initialize driver and device */
    /* called (indirectly) from sysHwInit2() */
    /* may be empty function [nullDrv()] for normal drivers */
    void (*devInstanceInit)
        (
        struct vxbDev * pDevInfo    /* device info */
        );

    /* initialize driver and device - second level */
    /* called (indirectly) from sysHwInit2() */
    /* may be empty function [nullDrv()] for bus controller drivers */
    void (*devInstanceInit2)
        (
        struct vxbDev * pDevInfo    /* device info */
        );

    /* connect to higher level entity */
    /* called (indirectly) at the end of sysHwInit2() */
    /* may be empty function [nullDrv()] for bus controllers */
    void (*devInstanceConnect)
        (
        struct vxbDev * pDevInfo    /* device info */
        );

    };

/*
 *  The following structures are used during bus and device
 *  configuration.  Drivers must have already registered with
 *  the bus subsystem.  This information is used during the
 *  bus probe and enumeration phase.
 *
 *  Note that the bus subsystem provides a pCookie pointer,
 *  which can optionally be used by the specific bus
 *  implementation.
 */

struct vxbDev
    {
    /* for bus subsystem internal use */

    struct vxbDev * pNext;
    struct vxbBusPresent * pParentBus; /* parent bus */
    UINT32      versionCounter; /* version number */

    /* access functions for use by driver */

    struct vxbAccessList * pAccess;

    /* access functions provided by driver */

    struct vxbDeviceMethod * pMethods;

    /* register base addresses */

    void *      pRegBase[10];

    /* bus-specific information */

    union
        {
        struct vxbBusPresent * pSubordinateBus;
        void *          pDevPrivate;
        }       u;

    void *      pBusSpecificDevInfo;
    UINT32      busID;

    /* interrupt information */

    void *      pIntrInfo;

    /* device name */

    char *      pName;

    /* driver registration info */

    struct vxbDevRegInfo * pDriver;

    /* per-driver info */

    void *      pDrvCtrl;

    };

/* hcfResource.hcfType values */
#define HCF_RES_STRING  1
#define HCF_RES_INT 2
#define HCF_RES_ADDR    3
#define RES_STRING  1
#define RES_INT 2
#define RES_ADDR    3

/* global data */

/* vxBus methods */

IMPORT char paramArraySet_desc[];
IMPORT char paramListSet_desc[];

IMPORT struct vxbAccessList * _archAccessFuncs;

/* forward declarations */

IMPORT STATUS vxbDriverUnregister(struct vxbDevRegInfo *pDriver);
IMPORT char * vxbBusTypeString(int busType);
IMPORT struct vxbDev * vxbDevStructAlloc(int flags);
IMPORT void vxbDevStructFree(struct vxbDev * pDev);

IMPORT STATUS vxbIntConnect
    (
    struct vxbDev * pDev,
    int         index,
    VOIDFUNCPTR     pIsr,
    void *      pArg
    );
IMPORT STATUS vxbIntDisconnect
    (
    struct vxbDev * pDev,
    int         index,
    VOIDFUNCPTR     pIsr,
    void *      pArg
    );
IMPORT STATUS vxbIntEnable
    (
    struct vxbDev * pDev,
    int         index,
    VOIDFUNCPTR     pIsr,
    void *      pArg
    );
IMPORT STATUS vxbIntDisable
    (
    struct vxbDev * pDev,
    int         index,
    VOIDFUNCPTR     pIsr,
    void *      pArg
    );

IMPORT STATUS vxbDevRegister
    (
    struct vxbDevRegInfo * pDevInfo /* per-bus recognition info */
    );

IMPORT STATUS   vxbBusTypeRegister
    (
    struct vxbBusTypeInfo * pBusType
    );

IMPORT  STATUS vxbBusTypeUnregister
    (
    struct vxbBusTypeInfo * pBusType
    );

IMPORT STATUS vxbDevError();    /* driver does not support specified functionality */
IMPORT STATUS nullDrv();        /* no action required */
IMPORT BOOL noDev();            /* returns FALSE */

IMPORT STATUS vxbBusAnnounce
    (
    struct vxbDev * pBusDev,    /* bus controller */
    UINT32      busID           /* bus type */
    );
IMPORT STATUS vxbDeviceAnnounce
    (
    struct vxbDev *     pBusDev
    );

IMPORT	STATUS vxbDevRemovalAnnounce
    (
    struct vxbDev *	pBusDev  
    );

IMPORT STATUS vxbLibInit();

IMPORT STATUS vxbDevMethodRun
    (
    UINT32      method,
    void *              pArg
    );
IMPORT FUNCPTR vxbDevMethodGet(struct vxbDev * pDev, UINT32 method);
IMPORT STATUS vxbDevIterate
    (
    FUNCPTR     func,           /* function to call */
    void *      pArg,           /* 2nd argument to func */
    UINT32      flags           /* flags to determine what to do */
    );
IMPORT STATUS vxbDevPath
    (
    struct vxbDev *     pBusDev,        /* device */
    FUNCPTR             func,           /* func @ each ctlr */
    void *              pArg            /* 2nd arg to func */
    );
IMPORT void vxBusShow(int verboseLevel);

IMPORT STATUS vxbInit();
IMPORT STATUS vxbDevInit();
IMPORT STATUS vxbDevConnect();
struct vxbDev * vxbDevParent(struct vxbDev * pDev);

struct vxbAccessList * vxbAccessListGet
    (
    struct vxbDev *     pDev
    );

FUNCPTR vxbAccessMethodGet
    (
    struct vxbDev * pDev,
    UINT32      accessType
    );

/*
 *  The following structure is used during configuration.  The
 *  BSP provides interrupt routing information in a table containing
 *  the routines that drivers use to enable, disable, and acknowledge
 *  interrupts on interrupt controllers between the device and the
 *  driver.
 *
 *  It's possible that this information may be kept on a per-device
 *  basis.
 *
 *  The configuration file contains a reference to this information,
 *  and stores the information in the HCF record for any device.
 *  The interrupt vector/irq information is extracted from the HCF
 *  record by the routine devResourceIntrGet(), which also checks
 *  for this information.
 */

struct hwIntRoute
    {
    /*
     * NOTE: if the following entries are modified, you must
     * also modify the busAccessList structure, above.
     */

    /* ensure that the bus controller does not prevent the specified interrupt */

    STATUS (*busIntEnable)
        (
        struct vxbDev * pDevInfo,   /* device info */
        int     intNo,              /* additional vector info */
        VOIDFUNCPTR pISR,           /* IRQ */
        void *      pArg
        );

    STATUS (*busIntDisable)
        (
        struct vxbDev * pDevInfo,   /* device info */
        int     intNo,              /* additional vector info */
        VOIDFUNCPTR pISR,           /* IRQ */
        void *      pArg
        );

    /* clear interrupt on bus controller */

    STATUS (*busIntAcknowledge)
        (
        struct vxbDev * pDevInfo,   /* device info */
        int     intNo,              /* additional vector info */
        VOIDFUNCPTR pISR,           /* IRQ */
        void *      pArg
        );
    };

#ifdef __cplusplus
}
#endif

#endif /* _INC_BUSLIB_H */





